//===============================================================================
// Microsoft patterns & practices Enterprise Library Contribution
// Query Application Block
//===============================================================================

using System;
using System.Diagnostics.CodeAnalysis;
using Microsoft.Practices.EnterpriseLibrary.Common.Instrumentation;

namespace EntLibContrib.Query.Instrumentation
{
	/// <summary>
	/// Defines the logical events that can be instrumented for the query block.
	/// </summary>
	/// <remarks>
	/// The concrete instrumentation is provided by an object bound to the events of the provider.
	/// The default listener, automatically bound during construction, is <see cref="QueryInstrumentationListener"/>.
	/// </remarks>
	[InstrumentationListener(typeof(QueryInstrumentationListener))]
	public class QueryInstrumentationProvider
	{
		#region Events
		/// <summary>
		/// Occurs when a read action is performed in an <see cref="IQuery"/>.
		/// </summary>
		[InstrumentationProvider("QueryRead")]
		public event EventHandler<QueryReadEventArgs> QueryRead;

		/// <summary>
		/// Occurs when a write action is performed in an <see cref="IQuery"/>.
		/// </summary>
		[InstrumentationProvider("QueryWrite")]
		public event EventHandler<QueryWriteEventArgs> QueryWrite;

		/// <summary>
		/// Occurs when a failure occurs in a <see cref="IQuery"/>.
		/// </summary>
		[InstrumentationProvider("QueryFailed")]
		public event EventHandler<QueryFailureEventArgs> QueryFailed;
		#endregion

		#region Public Methods
		/// <summary>
		/// Fires the <see cref="QueryInstrumentationProvider.QueryRead"/> event.
		/// </summary>
		/// <param name="queryType">Type of the query.</param>
		/// <param name="readCount">The read count.</param>
		[SuppressMessage("Microsoft.Design", "CA1030:UseEventsWhereAppropriate")]
		public void FireQueryRead(QueryType queryType, long readCount)
		{
			if (QueryRead != null)
				QueryRead(this, new QueryReadEventArgs(queryType, readCount));
		}

		/// <summary>
		/// Fires the <see cref="QueryInstrumentationProvider.QueryWrite"/> event.
		/// </summary>
		/// <param name="queryType">Type of the query.</param>
		[SuppressMessage("Microsoft.Design", "CA1030:UseEventsWhereAppropriate")]
		public void FireQueryWrite(QueryType queryType)
		{
			if (QueryWrite != null)
				QueryWrite(this, new QueryWriteEventArgs(queryType));
		}

		/// <summary>
		/// Fires the <see cref="QueryInstrumentationProvider.QueryFailed"/> event.
		/// </summary>
		/// <param name="errorMessage">The message that describes the failure.</param>
		/// <param name="exception">The message that represents the exception causing the failure.</param>
		[SuppressMessage("Microsoft.Design", "CA1030:UseEventsWhereAppropriate")]
		public void FireQueryFailed(string errorMessage, Exception exception)
		{
			if (QueryFailed != null)
				QueryFailed(this, new QueryFailureEventArgs(errorMessage, exception));
		}
		#endregion
	}
}